﻿// --------------------------------------------------------------------------------------------------------------------
// <copyright file="StudyDefinitionModule.cs" company="ELEN 7045 GROUP II">>
//   
// </copyright>
// <summary>
//   Configures the StudyDefinition UI Module
// </summary>
// --------------------------------------------------------------------------------------------------------------------

namespace Presentation.Module.StudyDefinition
{
    #region

    using System;

    using Application.Interfaces;
    using Application.StudyDefinition;

    using Domain.StudyDefinition.Contracts.DomainServices;
    using Domain.StudyDefinition.Contracts.Repositories.Studies;
    using Domain.StudyDefinition.Contracts.Repositories.SubjectGroups;
    using Domain.StudyDefinition.Contracts.Repositories.Treatments;
    using Domain.StudyDefinition.Services;

    using Infrastructure.Data.StudyDefinition.Repositories;

    using Microsoft.Practices.Unity;

    using Presentation.Module.StudyDefinition.Interfaces.Services;
    using Presentation.Module.StudyDefinition.Interfaces.ViewModels;
    using Presentation.Module.StudyDefinition.Interfaces.Views;
    using Presentation.Module.StudyDefinition.Services;
    using Presentation.Module.StudyDefinition.ViewModels;
    using Presentation.Module.StudyDefinition.Views;
    using Presentation.Shell.Interfaces;

    #endregion

    /// <summary>
    /// Configures the StudyDefinition UI Module
    /// </summary>
    public class StudyDefinitionModule : IPresentationModule
    {
        #region Constants and Fields

        /// <summary>
        /// A container instance.
        /// </summary>
        private readonly IUnityContainer containerInstance;

        #endregion

        #region Constructors and Destructors

        /// <summary>
        /// Initializes a new instance of the <see cref="StudyDefinitionModule"/> class.
        /// </summary>
        /// <param name="container">
        /// The container.
        /// </param>
        public StudyDefinitionModule(IUnityContainer container)
        {
            this.containerInstance = container;

            this.RegisterDependencies();
        }

        #endregion

        #region Properties

        /// <summary>
        /// Gets the default landing page for this module.
        /// </summary>
        public IModuleLandingPage LandingPage
        {
            get
            {
                    return this.containerInstance.Resolve<StudyDefinitionLandingPage>();
            }
        }

        /// <summary>
        /// Gets Name of the Module.
        /// </summary>
        public string Name
        {
            get
            {
                return "VPL Study Definition";
            }
        }

        #endregion

        #region Methods

        /// <summary>
        /// Registers the dependencies of the module
        /// This is a an area where the prototype could work better, one could remove the Fluent registration done in this
        /// method with a configuration file.
        /// The configuration file would also register all the dependencies immediately when the application starts up 
        /// instead of registering it when the module loads. 
        /// (Its something that needs to be weighed up though, improve performance in one place "module" and decrease it in another "app startup")
        /// Additionally not all modules require all the registrations so on may wish to find a better way to do this.
        /// </summary>
        private void RegisterDependencies()
        {
            this.containerInstance.RegisterType<ITreatmentRepository, TreatmentRepository>(
                new ContainerControlledLifetimeManager());
            this.containerInstance.RegisterType<ISubjectGroupRepository, SubjectGroupRepository>(
                new ContainerControlledLifetimeManager());
            this.containerInstance.RegisterType<IStudyRepository, StudyRepository>(
                new ContainerControlledLifetimeManager());


            // REGISTER DOMAIN SERVICES.
            this.containerInstance.RegisterType<IStudyTreatmentService, StudyTreatmentService>();

            this.containerInstance.RegisterType<IStudyDefinitionPreparationDomainService, StudyDefinitionPreparationDomainService>();

            this.containerInstance.RegisterType<IStudyInformationDisclosureDomainService, StudyInformationDisclosureDomainService>();
            this.containerInstance.RegisterType<ISubjectGroupInformationDisclosureDomainService, SubjectGroupInformationDisclosureDomainService>();
            this.containerInstance.RegisterType<ITreatmentInformationDisclosureDomainService, TreatmentInformationDisclosureDomainService>();
            this.containerInstance.RegisterType<IStudyMaintenanceDomainService, StudyMaintenanceDomainService>();
            this.containerInstance.RegisterType<ISubjectGroupMaintenanceDomainService, SubjectGroupMaintenanceDomainService>();
            this.containerInstance.RegisterType<ITreatmentMaintenanceDomainService, TreatmentMaintenanceDomainService>();

            // REGISTER APPLICATION MANAGEMENT SERVICES
            this.containerInstance.RegisterType<IStudyDefinitionManagementService, StudyDefinitionManagementService>(
                new ContainerControlledLifetimeManager());

            // Registering Presentation Studies service with the container
            this.containerInstance.RegisterType<IStudiesUIProxyService, StudiesUiProxyService>(new ContainerControlledLifetimeManager());

            //// Registering views and view models with container

            // TREATMENTS
            this.containerInstance.RegisterType<ITreatmentAddViewModel, TreatmentAddViewModel>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<ITreatmentAddView, TreatmentAddView>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<ITreatmentEditViewModel, TreatmentEditViewModel>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<ITreatmentEditView, TreatmentEditView>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<ITreatmentsViewModel, TreatmentsViewModel>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<Func<ITreatmentsView, TreatmentsView>>();
            this.containerInstance.RegisterType<ITreatmentsView, TreatmentsView>(
                new TransientLifetimeManager());

            // SUBJECT GROUPS

            // Automatic Factory implemented here (Playing around with code.)
            this.containerInstance.RegisterType<ISubjectGroupAddViewModel, SubjectGroupAddViewModel>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<ISubjectGroupAddView, SubjectGroupAddView>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<ISubjectGroupEditViewModel, SubjectGroupEditViewModel>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<ISubjectGroupEditView, SubjectGroupEditView>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<ISubjectGroupsViewModel, SubjectGroupsViewModel>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<ISubjectGroupsView, SubjectGroupsView>(
                new TransientLifetimeManager());

            // Automatic Factory implemented above.

            // STUDIES
            this.containerInstance.RegisterType<IStudyAddViewModel, StudyAddViewModel>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<IStudyAddView, StudyAddView>(
                new TransientLifetimeManager());

            this.containerInstance.RegisterType<IStudyEditViewModel, StudyEditViewModel>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<IStudyEditView, StudyEditView>(
                new TransientLifetimeManager());

            this.containerInstance.RegisterType<IStudiesViewModel, StudiesViewModel>(
                new TransientLifetimeManager());
            this.containerInstance.RegisterType<IStudiesView, StudiesView>(
                new TransientLifetimeManager());
        }

        #endregion
    }
}
